/*
 * Copyright (c) China Telecom Cloud Technology Co., Ltd. 2024-2025. All rights reserved.
 */
#include "../include/KVStorageClient.h"
#include "Common.h"

void KVStorageClient::init(FileSystem type, 
                        std::string path, 
                        void *addr,
                        std::string mountPath) {
    if (inited) {
        return;
    }
    fsType = type;
#if defined(USE_THREEFS)
    if (fsType != FileSystem::THREEFS) {
        LOG_ERROR_FMT("FileSystem must be FileSystem::THREEFS");
        throw std::runtime_error("Compiled with ThreeFS support only");
    }
    strategy = std::make_unique<ThreeFsStartegy>(mountPath, path, addr);
    if (static_cast<ThreeFsStartegy *>(strategy.get())->createIov() == KVC_OK) {
        inited = true;
    }
    LOG_INFO_FMT("Init 3FS.");
#elif defined(USE_POSIX)
    if (fsType != FileSystem::POSIX) {
        LOG_ERROR_FMT("FileSystem must be FileSystem::POSIX");
        throw std::runtime_error("Compiled with POSIX support only");
    }
    strategy = std::make_unique<PosixStartegy>(mountPath, path, addr);
    inited = true;
    LOG_INFO_FMT("Init POSIX. MountPath: {}", mountPath.c_str());
#elif defined(USE_LUSTRE)
    if (fsType != FileSystem::LUSTRE) {
        LOG_ERROR_FMT("FileSystem must be FileSystem::LUSTRE");
        throw std::runtime_error("Compiled with Lustre support only");
    }
    strategy = std::make_unique<LustreStartegy>(mountPath, path, addr);
    inited = true;
    LOG_INFO_FMT("Init LUSTRE.");
#endif
}

int32_t KVStorageClient::get(const std::string &objId, 
                            const Segment &segment,
                            const uint64_t srcOffset, 
                            const uint64_t dstOffset,
                            const uint64_t length
                        ) noexcept {
    LOG_DEBUG_FMT("get fileId: {}, offset: {}, "
                "length: {}, shmOff: {}", objId,
                dstOffset, length, segment.getOffset());
    
    // 获取原始指针并调用底层(具体的文件系统类型)实现
    return strategy.get()->get(objId, 
                            segment, 
                            srcOffset, 
                            dstOffset, 
                            length
                        );
}




int32_t KVStorageClient::put(const std::string &objId, 
                            const Segment &segment,
                            const uint64_t srcOffset, 
                            const uint64_t dstOffset,
                            const uint64_t length) noexcept {
    LOG_DEBUG_FMT("get fileId: {}, offset: {}, length: {}, "
        "shmOff: {}", objId, dstOffset, length, segment.getOffset());

    return strategy.get()->put(objId, 
                            segment, 
                            srcOffset, 
                            dstOffset, 
                            length
                        );
}




int32_t KVStorageClient::remove(
    const std::string &objId) noexcept {
    return strategy.get()->remove(objId);
}




bool KVStorageClient::isExist(
    const std::string &objId) noexcept {
    return strategy.get()->isExist(objId);
}